/*    
    LogParser - Log File Parser
    Copyright (C) 2007  Alois Kraus
  
    This source code is published under the Microsoft Permissive License (Ms-PL)
    http://www.microsoft.com/resources/sharedsource/licensingbasics/permissivelicense.mspx
*/


using System;
using System.Collections.Generic;
using System.Text;
using System.Text.RegularExpressions;
using System.IO;
using System.Globalization;
using Microsoft.Practices.EnterpriseLibrary.Common.Configuration;
using Microsoft.Practices.EnterpriseLibrary.Logging;
using System.Diagnostics;

namespace EntLibContrib.Logging.Parser
{

    /// <summary>
    /// It is a tokenizer but it could also be called LogEntry Deserializer. It does
    /// try to "deserialize" form a given text fragment LogEntry objects using regular
    /// expressions.
    /// </summary>
    public class Tokenizer : LogEntryParser
    {
        Dictionary<string, List<Regex>> myFileRegularExpressions;

        /// <summary>
        /// Initializes a new instance of the <see cref="Tokenizer"/> class.
        /// </summary>
        /// <param name="builder">The builder.</param>
        public Tokenizer(RegularExpressionBuilder builder)
        {
            Init(builder);
        }

        /// <summary>
        /// Initializes a new instance of the <see cref="Tokenizer"/> class.
        /// </summary>
        /// <param name="builder">The builder.</param>
        /// <param name="theTimeStampParser">The time stamp parser to use</param>
        public Tokenizer(RegularExpressionBuilder builder, ITimeStampParser theTimeStampParser)
            : base(theTimeStampParser)
        {
            Init(builder);
        }

        private void Init(RegularExpressionBuilder builder)
        {
            if (builder == null)
                throw new ArgumentNullException("builder");

            myFileRegularExpressions = builder.FileRegularExpressions;
        }


        /// <summary>
        /// Gets the parsed entries.
        /// </summary>
        /// <param name="messageText">The message text.</param>
        /// <param name="fileName">Name of the file.</param>
        /// <returns></returns>
        public IEnumerable<LogEntry> GetDeseralizedLogEntries(string messageText, string fileName)
        {
            if (messageText == null)
                throw new ArgumentNullException(messageText);

            // get regular expressions for configure file name
            List<Regex> rexList = myFileRegularExpressions[Path.GetFileName(fileName)];


            bool bMatch = false;
            foreach (Regex rex in rexList)
            {
                foreach (Match m in rex.Matches(messageText))
                {
                    bMatch = true;
                    yield return DeseralizeLogEntry(m);
                }
            }

            if (!bMatch)
            {
                // if the message could not be parsed we return it as whole.
                LogEntry unparsedEntry = new LogEntry();
                unparsedEntry.Severity = TraceEventType.Information;
                unparsedEntry.TimeStamp = DateTime.MinValue;
                unparsedEntry.Message = messageText;

                yield return unparsedEntry;
            }
        }
    }
}
